package main

import (
	"fmt"
	"sync"
	"time"

	"context"

	"github.com/go-redis/redis/v8"
)

var ctx = context.Background()

func incr() {
	rdb := redis.NewClient(&redis.Options{
		Addr:     "localhost:6379",
		Password: "",
		DB:       0,
	})

	var lockKey = "counter_lock"
	var counterKey = "counter"

	// lock
	resp := rdb.SetNX(ctx, lockKey, 1, time.Second*5)
	lockSuccess, err := resp.Result()
	if err != nil || !lockSuccess {
		fmt.Println(err, "lock result:", lockSuccess)
		return
	}
	// counter++
	getResp := rdb.Get(ctx, counterKey)
	cntValue, err := getResp.Int64()
	if err == redis.Nil {
		cntValue++
		resp := rdb.Set(ctx, counterKey, cntValue, 0)
		_, err := resp.Result()
		if err != nil {
			println("set value error!")
		}
	}
	println("current counter is ", cntValue)
	delResp := rdb.Del(ctx, lockKey)
	unlockSuccess, err := delResp.Result()
	if err == nil && unlockSuccess > 0 {
		println("unlock success")
	} else {
		println("unlock failed ", err)
	}
}

func main() {
	var wg sync.WaitGroup
	for i := 0; i < 10; i++ {
		wg.Add(1)
		go func() {
			defer wg.Done()
			incr()
		}()
	}

	wg.Wait()
}
